/*
	d3d9cutter.h: Direct3D proxy code for rotating the screen (amungst other things)

	Copyright (c) 2010, James Lee (jbit<at>jbit<dot>net)
	All rights reserved.

	Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:

	Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
	Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
	Neither the name of the copyright holder nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.
	THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.	
*/
#ifndef _D3DCUTTER_D3D9CUTTER_H_
#define _D3DCUTTER_D3D9CUTTER_H_ 1

class IDirect3D9Cutter : public IDirect3D9
{
private:
   	IDirect3D9* m_real;

public:
	IDirect3D9Cutter(IDirect3D9 *real) : m_real(real)
	{
	}

	virtual ~IDirect3D9Cutter(void)
	{
	}

	// IUnknown
	HRESULT __stdcall QueryInterface(REFIID riid, void** ppvObj);
	ULONG __stdcall AddRef(void);
	ULONG __stdcall Release(void);

	// IDirect3D9
	HRESULT __stdcall RegisterSoftwareDevice(void* pInitializeFunction)
	{
		return m_real->RegisterSoftwareDevice(pInitializeFunction);
	}

	UINT __stdcall GetAdapterCount(void)
	{
		return m_real->GetAdapterCount();
	}

	HRESULT __stdcall GetAdapterIdentifier(UINT Adapter,DWORD Flags, D3DADAPTER_IDENTIFIER9* pIdentifier)
	{
		return m_real->GetAdapterIdentifier(Adapter,Flags,pIdentifier);
	}

	UINT __stdcall GetAdapterModeCount(UINT Adapter, D3DFORMAT Format)
	{
		return m_real->GetAdapterModeCount(Adapter, Format);
	}

	HRESULT __stdcall EnumAdapterModes(UINT Adapter, D3DFORMAT Format, UINT Mode,D3DDISPLAYMODE* pMode)
	{
		return m_real->EnumAdapterModes(Adapter,Format,Mode,pMode);
	}

	HRESULT __stdcall GetAdapterDisplayMode(UINT Adapter, D3DDISPLAYMODE* pMode)
	{
		return m_real->GetAdapterDisplayMode(Adapter,pMode);
	}
	
	HRESULT __stdcall CheckDeviceType(UINT iAdapter, D3DDEVTYPE DevType, D3DFORMAT DisplayFormat, D3DFORMAT BackBufferFormat, BOOL bWindowed)
	{
		return m_real->CheckDeviceType(iAdapter,DevType,DisplayFormat,BackBufferFormat,bWindowed);
	}

	HRESULT __stdcall CheckDeviceFormat(UINT Adapter, D3DDEVTYPE DeviceType, D3DFORMAT AdapterFormat, DWORD Usage, D3DRESOURCETYPE RType, D3DFORMAT CheckFormat)
	{
		return m_real->CheckDeviceFormat(Adapter,DeviceType,AdapterFormat,Usage,RType,CheckFormat);
	}

	HRESULT __stdcall CheckDeviceMultiSampleType(UINT Adapter, D3DDEVTYPE DeviceType, D3DFORMAT SurfaceFormat, BOOL Windowed, D3DMULTISAMPLE_TYPE MultiSampleType, DWORD* pQualityLevels)
	{
		return m_real->CheckDeviceMultiSampleType(Adapter,DeviceType,SurfaceFormat,Windowed,MultiSampleType,pQualityLevels);
	}

	HRESULT __stdcall CheckDepthStencilMatch(UINT Adapter, D3DDEVTYPE DeviceType, D3DFORMAT AdapterFormat, D3DFORMAT RenderTargetFormat, D3DFORMAT DepthStencilFormat)
	{
		return m_real->CheckDepthStencilMatch(Adapter,DeviceType,AdapterFormat,RenderTargetFormat,DepthStencilFormat);
	}

	HRESULT __stdcall CheckDeviceFormatConversion(UINT Adapter, D3DDEVTYPE DeviceType, D3DFORMAT SourceFormat, D3DFORMAT TargetFormat)
	{
		return m_real->CheckDeviceFormatConversion(Adapter,DeviceType,SourceFormat,TargetFormat);
	}

	HRESULT __stdcall GetDeviceCaps(UINT Adapter, D3DDEVTYPE DeviceType, D3DCAPS9* pCaps)
	{
		return m_real->GetDeviceCaps(Adapter,DeviceType,pCaps);
	}

	HMONITOR __stdcall GetAdapterMonitor(UINT Adapter)
	{
		return m_real->GetAdapterMonitor(Adapter);
	}

	HRESULT __stdcall CreateDevice(UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags, D3DPRESENT_PARAMETERS* pPresentationParameters, IDirect3DDevice9** ppReturnedDeviceInterface);
};


class IDirect3DDevice9Cutter : public IDirect3DDevice9
{
private:
	IDirect3DDevice9* m_real;
	IDirect3DTexture9 *m_renderTexture;
	IDirect3DSurface9 *m_renderSurface;
	IDirect3DStateBlock9 *m_stateBlock;
	size_t m_width, m_height;
	unsigned int m_curMode;
	size_t m_lastCount;
	size_t m_clearCount; // Stupid mode detection for th10->12
	int m_autoGame, m_autoMenu;

	size_t m_vertexBufferCount;
	IDirect3DVertexBuffer9 *m_vertexBuffer[16];
	size_t m_vertexBufferSize[16];
	unsigned int m_vertexBufferFlags[16];

public:
	IDirect3DDevice9Cutter(IDirect3DDevice9* pOriginal);
	virtual ~IDirect3DDevice9Cutter(void);

	// IUnknown
	HRESULT __stdcall QueryInterface (REFIID riid, void** ppvObj);
	ULONG   __stdcall AddRef(void);
	ULONG   __stdcall Release(void);

	// IDirect3DDevice9
	HRESULT __stdcall TestCooperativeLevel(void)
	{
		return m_real->TestCooperativeLevel();
	}

	UINT __stdcall GetAvailableTextureMem(void)
	{
		return m_real->GetAvailableTextureMem();
	}

	HRESULT __stdcall EvictManagedResources(void)
	{
		return m_real->EvictManagedResources();
	}

	HRESULT __stdcall GetDirect3D(IDirect3D9** ppD3D9)
	{
		return m_real->GetDirect3D(ppD3D9);
	}

	HRESULT __stdcall GetDeviceCaps(D3DCAPS9* pCaps)
	{
		return m_real->GetDeviceCaps(pCaps);
	}

	HRESULT __stdcall GetDisplayMode(UINT iSwapChain,D3DDISPLAYMODE* pMode)
	{
		return m_real->GetDisplayMode(iSwapChain, pMode);
	}

	HRESULT __stdcall GetCreationParameters(D3DDEVICE_CREATION_PARAMETERS *pParameters)
	{
		return m_real->GetCreationParameters(pParameters);
	}

	HRESULT __stdcall SetCursorProperties(UINT XHotSpot,UINT YHotSpot,IDirect3DSurface9* pCursorBitmap)
	{
		return m_real->SetCursorProperties(XHotSpot,YHotSpot,pCursorBitmap);
	}

	void __stdcall SetCursorPosition(int X,int Y,DWORD Flags)
	{
		return m_real->SetCursorPosition(X,Y,Flags);
	}

	BOOL __stdcall ShowCursor(BOOL bShow)
	{
		return m_real->ShowCursor(bShow);
	}

	HRESULT __stdcall CreateAdditionalSwapChain(D3DPRESENT_PARAMETERS* pPresentationParameters,IDirect3DSwapChain9** pSwapChain)  
	{
		return m_real->CreateAdditionalSwapChain(pPresentationParameters,pSwapChain);
	}

	HRESULT __stdcall GetSwapChain(UINT iSwapChain,IDirect3DSwapChain9** pSwapChain)
	{
		return m_real->GetSwapChain(iSwapChain,pSwapChain);
	}

	UINT __stdcall GetNumberOfSwapChains(void)
	{
		return m_real->GetNumberOfSwapChains();
	}

	HRESULT __stdcall Reset(D3DPRESENT_PARAMETERS* pPresentationParameters)
	{
		return m_real->Reset(pPresentationParameters);
	}

	HRESULT __stdcall Present(CONST RECT* pSourceRect,CONST RECT* pDestRect,HWND hDestWindowOverride,CONST RGNDATA* pDirtyRegion);
	HRESULT __stdcall GetBackBuffer(UINT iSwapChain,UINT iBackBuffer,D3DBACKBUFFER_TYPE Type,IDirect3DSurface9** ppBackBuffer);

	HRESULT __stdcall GetRasterStatus(UINT iSwapChain,D3DRASTER_STATUS* pRasterStatus)
	{
		return m_real->GetRasterStatus(iSwapChain,pRasterStatus);
	}

	HRESULT __stdcall SetDialogBoxMode(BOOL bEnableDialogs)
	{
		return m_real->SetDialogBoxMode(bEnableDialogs);
	}

	void __stdcall SetGammaRamp(UINT iSwapChain,DWORD Flags,CONST D3DGAMMARAMP* pRamp)
	{
		return m_real->SetGammaRamp(iSwapChain,Flags,pRamp);
	}

	void __stdcall GetGammaRamp(UINT iSwapChain,D3DGAMMARAMP* pRamp)
	{
		return m_real->GetGammaRamp(iSwapChain,pRamp);
	}

	HRESULT __stdcall CreateTexture(UINT Width,UINT Height,UINT Levels,DWORD Usage,D3DFORMAT Format,D3DPOOL Pool,IDirect3DTexture9** ppTexture,HANDLE* pSharedHandle)
	{
		return m_real->CreateTexture(Width,Height,Levels,Usage,Format,Pool,ppTexture,pSharedHandle);
	}

	HRESULT __stdcall CreateVolumeTexture(UINT Width,UINT Height,UINT Depth,UINT Levels,DWORD Usage,D3DFORMAT Format,D3DPOOL Pool,IDirect3DVolumeTexture9** ppVolumeTexture,HANDLE* pSharedHandle)
	{
		return m_real->CreateVolumeTexture(Width,Height,Depth,Levels,Usage,Format,Pool,ppVolumeTexture,pSharedHandle);
	}

	HRESULT __stdcall CreateCubeTexture(UINT EdgeLength,UINT Levels,DWORD Usage,D3DFORMAT Format,D3DPOOL Pool,IDirect3DCubeTexture9** ppCubeTexture,HANDLE* pSharedHandle)
	{
		return m_real->CreateCubeTexture(EdgeLength,Levels,Usage,Format,Pool,ppCubeTexture,pSharedHandle);
	}

	HRESULT __stdcall CreateVertexBuffer(UINT Length,DWORD Usage,DWORD FVF,D3DPOOL Pool,IDirect3DVertexBuffer9** ppVertexBuffer,HANDLE* pSharedHandle)
	{
		return m_real->CreateVertexBuffer(Length,Usage,FVF,Pool,ppVertexBuffer,pSharedHandle);
	}

	HRESULT __stdcall CreateIndexBuffer(UINT Length,DWORD Usage,D3DFORMAT Format,D3DPOOL Pool,IDirect3DIndexBuffer9** ppIndexBuffer,HANDLE* pSharedHandle)
	{
		return m_real->CreateIndexBuffer(Length,Usage,Format,Pool,ppIndexBuffer,pSharedHandle);
	}

	HRESULT __stdcall CreateRenderTarget(UINT Width,UINT Height,D3DFORMAT Format,D3DMULTISAMPLE_TYPE MultiSample,DWORD MultisampleQuality,BOOL Lockable,IDirect3DSurface9** ppSurface,HANDLE* pSharedHandle)
	{
		return m_real->CreateRenderTarget(Width,Height,Format,MultiSample,MultisampleQuality,Lockable,ppSurface,pSharedHandle);
	}

	HRESULT __stdcall CreateDepthStencilSurface(UINT Width,UINT Height,D3DFORMAT Format,D3DMULTISAMPLE_TYPE MultiSample,DWORD MultisampleQuality,BOOL Discard,IDirect3DSurface9** ppSurface,HANDLE* pSharedHandle)
	{
		return m_real->CreateDepthStencilSurface(Width,Height,Format,MultiSample,MultisampleQuality,Discard,ppSurface,pSharedHandle);
	}

	HRESULT __stdcall UpdateSurface(IDirect3DSurface9* pSourceSurface,CONST RECT* pSourceRect,IDirect3DSurface9* pDestinationSurface,CONST POINT* pDestPoint)
	{
		return m_real->UpdateSurface(pSourceSurface,pSourceRect,pDestinationSurface,pDestPoint);
	}

	HRESULT __stdcall UpdateTexture(IDirect3DBaseTexture9* pSourceTexture,IDirect3DBaseTexture9* pDestinationTexture)
	{
		return m_real->UpdateTexture(pSourceTexture,pDestinationTexture);
	}

	HRESULT __stdcall GetRenderTargetData(IDirect3DSurface9* pRenderTarget,IDirect3DSurface9* pDestSurface)
	{
		return m_real->GetRenderTargetData(pRenderTarget,pDestSurface);
	}

	HRESULT __stdcall GetFrontBufferData(UINT iSwapChain,IDirect3DSurface9* pDestSurface)
	{
		return m_real->GetFrontBufferData(iSwapChain,pDestSurface);
	}

	HRESULT __stdcall StretchRect(IDirect3DSurface9* pSourceSurface,CONST RECT* pSourceRect,IDirect3DSurface9* pDestSurface,CONST RECT* pDestRect,D3DTEXTUREFILTERTYPE Filter)
	{
		return m_real->StretchRect(pSourceSurface,pSourceRect,pDestSurface,pDestRect,Filter);
	}

	HRESULT __stdcall ColorFill(IDirect3DSurface9* pSurface,CONST RECT* pRect,D3DCOLOR color)
	{
		return m_real->ColorFill(pSurface,pRect,color);
	}

	HRESULT __stdcall CreateOffscreenPlainSurface(UINT Width,UINT Height,D3DFORMAT Format,D3DPOOL Pool,IDirect3DSurface9** ppSurface,HANDLE* pSharedHandle)
	{
		return m_real->CreateOffscreenPlainSurface(Width,Height,Format,Pool,ppSurface,pSharedHandle);
	}

	HRESULT __stdcall SetRenderTarget(DWORD RenderTargetIndex,IDirect3DSurface9* pRenderTarget)
	{
		return m_real->SetRenderTarget(RenderTargetIndex,pRenderTarget);
	}

	HRESULT __stdcall GetRenderTarget(DWORD RenderTargetIndex,IDirect3DSurface9** ppRenderTarget)
	{
		return m_real->GetRenderTarget(RenderTargetIndex,ppRenderTarget);
	}
	
	HRESULT __stdcall SetDepthStencilSurface(IDirect3DSurface9* pNewZStencil)
	{
		return m_real->SetDepthStencilSurface(pNewZStencil);
	}

	HRESULT __stdcall GetDepthStencilSurface(IDirect3DSurface9** ppZStencilSurface)
	{
		return m_real->GetDepthStencilSurface(ppZStencilSurface);
	}

	HRESULT __stdcall BeginScene(void)
	{
		return m_real->BeginScene();
	}

	HRESULT __stdcall EndScene(void);

	HRESULT __stdcall Clear(DWORD Count,CONST D3DRECT* pRects,DWORD Flags,D3DCOLOR Color,float Z,DWORD Stencil)
	{
		m_clearCount++;
		return m_real->Clear(Count,pRects,Flags,Color,Z,Stencil);
	}

	HRESULT __stdcall SetTransform(D3DTRANSFORMSTATETYPE State,CONST D3DMATRIX* pMatrix)
	{
		return m_real->SetTransform(State,pMatrix);
	}

	HRESULT __stdcall GetTransform(D3DTRANSFORMSTATETYPE State,D3DMATRIX* pMatrix)
	{
		return m_real->GetTransform(State,pMatrix);
	}

	HRESULT __stdcall MultiplyTransform(D3DTRANSFORMSTATETYPE State,CONST D3DMATRIX* pMatrix)
	{
		return m_real->MultiplyTransform(State,pMatrix);
	}

	HRESULT __stdcall SetViewport(CONST D3DVIEWPORT9* pViewport)
	{
		return m_real->SetViewport(pViewport);
	}

	HRESULT __stdcall GetViewport(D3DVIEWPORT9* pViewport)
	{
		return m_real->GetViewport(pViewport);
	}

	HRESULT __stdcall SetMaterial(CONST D3DMATERIAL9* pMaterial)
	{
		return m_real->SetMaterial(pMaterial);
	}

	HRESULT __stdcall GetMaterial(D3DMATERIAL9* pMaterial)
	{
		return m_real->GetMaterial(pMaterial);
	}

	HRESULT __stdcall SetLight(DWORD Index,CONST D3DLIGHT9* pLight)
	{
		return m_real->SetLight(Index,pLight);
	}

	HRESULT __stdcall GetLight(DWORD Index,D3DLIGHT9* pLight)
	{
		return m_real->GetLight(Index,pLight);
	}

	HRESULT __stdcall LightEnable(DWORD Index,BOOL Enable)
	{
		return m_real->LightEnable(Index,Enable);
	}

	HRESULT __stdcall GetLightEnable(DWORD Index,BOOL* pEnable)
	{
		return m_real->GetLightEnable(Index, pEnable);
	}

	HRESULT __stdcall SetClipPlane(DWORD Index,CONST float* pPlane)
	{
		return m_real->SetClipPlane(Index, pPlane);
	}

	HRESULT __stdcall GetClipPlane(DWORD Index,float* pPlane)
	{
		return m_real->GetClipPlane(Index,pPlane);
	}

	HRESULT __stdcall SetRenderState(D3DRENDERSTATETYPE State,DWORD Value)
	{
		return m_real->SetRenderState(State, Value);
	}

	HRESULT __stdcall GetRenderState(D3DRENDERSTATETYPE State,DWORD* pValue)
	{
		return m_real->GetRenderState(State, pValue);
	}

	HRESULT __stdcall CreateStateBlock(D3DSTATEBLOCKTYPE Type,IDirect3DStateBlock9** ppSB)
	{
		return m_real->CreateStateBlock(Type,ppSB);
	}

	HRESULT __stdcall BeginStateBlock(void)
	{
		return m_real->BeginStateBlock();
	}

	HRESULT __stdcall EndStateBlock(IDirect3DStateBlock9** ppSB)
	{
		return m_real->EndStateBlock(ppSB);
	}

	HRESULT __stdcall SetClipStatus(CONST D3DCLIPSTATUS9* pClipStatus)
	{
		return m_real->SetClipStatus(pClipStatus);
	}

	HRESULT __stdcall GetClipStatus(D3DCLIPSTATUS9* pClipStatus)
	{
		return m_real->GetClipStatus( pClipStatus);
	}

	HRESULT __stdcall GetTexture(DWORD Stage,IDirect3DBaseTexture9** ppTexture)
	{
		return m_real->GetTexture(Stage,ppTexture);
	}

	HRESULT __stdcall SetTexture(DWORD Stage,IDirect3DBaseTexture9* pTexture)
	{
		return m_real->SetTexture(Stage,pTexture);
	}

	HRESULT __stdcall GetTextureStageState(DWORD Stage,D3DTEXTURESTAGESTATETYPE Type,DWORD* pValue)
	{
		return m_real->GetTextureStageState(Stage,Type, pValue);
	}

	HRESULT __stdcall SetTextureStageState(DWORD Stage,D3DTEXTURESTAGESTATETYPE Type,DWORD Value)
	{
		return m_real->SetTextureStageState(Stage,Type,Value);
	}

	HRESULT __stdcall GetSamplerState(DWORD Sampler,D3DSAMPLERSTATETYPE Type,DWORD* pValue)
	{
		return m_real->GetSamplerState(Sampler,Type, pValue);
	}

	HRESULT __stdcall SetSamplerState(DWORD Sampler,D3DSAMPLERSTATETYPE Type,DWORD Value)
	{
		return m_real->SetSamplerState(Sampler,Type,Value);
	}

	HRESULT __stdcall ValidateDevice(DWORD* pNumPasses)
	{
		return m_real->ValidateDevice( pNumPasses);
	}

	HRESULT __stdcall SetPaletteEntries(UINT PaletteNumber,CONST PALETTEENTRY* pEntries)
	{
		return m_real->SetPaletteEntries(PaletteNumber, pEntries);
	}

	HRESULT __stdcall GetPaletteEntries(UINT PaletteNumber,PALETTEENTRY* pEntries)
	{
		return m_real->GetPaletteEntries(PaletteNumber, pEntries);
	}

	HRESULT __stdcall SetCurrentTexturePalette(UINT PaletteNumber)
	{
		return m_real->SetCurrentTexturePalette(PaletteNumber);
	}

	HRESULT __stdcall GetCurrentTexturePalette(UINT *PaletteNumber)
	{
		return m_real->GetCurrentTexturePalette(PaletteNumber);
	}

	HRESULT __stdcall SetScissorRect(CONST RECT* pRect)
	{
		return m_real->SetScissorRect( pRect);
	}

	HRESULT __stdcall GetScissorRect( RECT* pRect)
	{
		return m_real->GetScissorRect( pRect);
	}

	HRESULT __stdcall SetSoftwareVertexProcessing(BOOL bSoftware)
	{
		return m_real->SetSoftwareVertexProcessing(bSoftware);
	}

	BOOL __stdcall GetSoftwareVertexProcessing(void)
	{
		return m_real->GetSoftwareVertexProcessing();
	}

	HRESULT __stdcall SetNPatchMode(float nSegments)
	{
		return m_real->SetNPatchMode(nSegments);
	}

	float __stdcall GetNPatchMode(void)
	{
		return m_real->GetNPatchMode();
	}

	HRESULT __stdcall DrawPrimitive(D3DPRIMITIVETYPE PrimitiveType,UINT StartVertex,UINT PrimitiveCount)
	{
		return m_real->DrawPrimitive(PrimitiveType,StartVertex,PrimitiveCount);
	}

	HRESULT __stdcall DrawIndexedPrimitive(D3DPRIMITIVETYPE PrimitiveType,INT BaseVertexIndex,UINT MinVertexIndex,UINT NumVertices,UINT startIndex,UINT primCount)
	{
		return m_real->DrawIndexedPrimitive(PrimitiveType,BaseVertexIndex,MinVertexIndex,NumVertices,startIndex,primCount);
	}

	HRESULT __stdcall DrawPrimitiveUP(D3DPRIMITIVETYPE PrimitiveType,UINT PrimitiveCount,CONST void* pVertexStreamZeroData,UINT VertexStreamZeroStride)
	{
		return m_real->DrawPrimitiveUP(PrimitiveType,PrimitiveCount,pVertexStreamZeroData,VertexStreamZeroStride);
	}

	HRESULT __stdcall DrawIndexedPrimitiveUP(D3DPRIMITIVETYPE PrimitiveType,UINT MinVertexIndex,UINT NumVertices,UINT PrimitiveCount,CONST void* pIndexData,D3DFORMAT IndexDataFormat,CONST void* pVertexStreamZeroData,UINT VertexStreamZeroStride)
	{
		return m_real->DrawIndexedPrimitiveUP(PrimitiveType,MinVertexIndex,NumVertices,PrimitiveCount, pIndexData, IndexDataFormat, pVertexStreamZeroData,VertexStreamZeroStride);
	}

	HRESULT __stdcall ProcessVertices(UINT SrcStartIndex,UINT DestIndex,UINT VertexCount,IDirect3DVertexBuffer9* pDestBuffer,IDirect3DVertexDeclaration9* pVertexDecl,DWORD Flags)
	{
		return m_real->ProcessVertices( SrcStartIndex, DestIndex, VertexCount, pDestBuffer, pVertexDecl, Flags);
	}

	HRESULT __stdcall CreateVertexDeclaration(CONST D3DVERTEXELEMENT9* pVertexElements,IDirect3DVertexDeclaration9** ppDecl)
	{
		return m_real->CreateVertexDeclaration( pVertexElements,ppDecl);
	}

	HRESULT __stdcall SetVertexDeclaration(IDirect3DVertexDeclaration9* pDecl)
	{
		return m_real->SetVertexDeclaration(pDecl);
	}

	HRESULT __stdcall GetVertexDeclaration(IDirect3DVertexDeclaration9** ppDecl)
	{
		return m_real->GetVertexDeclaration(ppDecl);
	}

	HRESULT __stdcall SetFVF(DWORD FVF)
	{
		return m_real->SetFVF(FVF);
	}

	HRESULT __stdcall GetFVF(DWORD* pFVF)
	{
		return m_real->GetFVF(pFVF);
	}

	HRESULT __stdcall CreateVertexShader(CONST DWORD* pFunction,IDirect3DVertexShader9** ppShader)
	{
		return m_real->CreateVertexShader(pFunction,ppShader);
	}

	HRESULT __stdcall SetVertexShader(IDirect3DVertexShader9* pShader)
	{
		return m_real->SetVertexShader(pShader);
	}

	HRESULT __stdcall GetVertexShader(IDirect3DVertexShader9** ppShader)
	{
		return m_real->GetVertexShader(ppShader);
	}

	HRESULT __stdcall SetVertexShaderConstantF(UINT StartRegister,CONST float* pConstantData,UINT Vector4fCount)
	{
		return m_real->SetVertexShaderConstantF(StartRegister,pConstantData, Vector4fCount);
	}

	HRESULT __stdcall GetVertexShaderConstantF(UINT StartRegister,float* pConstantData,UINT Vector4fCount)
	{
		return m_real->GetVertexShaderConstantF(StartRegister,pConstantData,Vector4fCount);
	}

	HRESULT __stdcall SetVertexShaderConstantI(UINT StartRegister,CONST int* pConstantData,UINT Vector4iCount)
	{
		return m_real->SetVertexShaderConstantI(StartRegister,pConstantData,Vector4iCount);
	}

	HRESULT __stdcall GetVertexShaderConstantI(UINT StartRegister,int* pConstantData,UINT Vector4iCount)
	{
		return m_real->GetVertexShaderConstantI(StartRegister,pConstantData,Vector4iCount);
	}

	HRESULT __stdcall SetVertexShaderConstantB(UINT StartRegister,CONST BOOL* pConstantData,UINT  BoolCount)
	{
		return m_real->SetVertexShaderConstantB(StartRegister,pConstantData,BoolCount);
	}

	HRESULT __stdcall GetVertexShaderConstantB(UINT StartRegister,BOOL* pConstantData,UINT BoolCount)
	{
		return m_real->GetVertexShaderConstantB(StartRegister,pConstantData,BoolCount);
	}

	HRESULT __stdcall SetStreamSource(UINT StreamNumber,IDirect3DVertexBuffer9* pStreamData,UINT OffsetInBytes,UINT Stride)
	{
		return m_real->SetStreamSource(StreamNumber,pStreamData,OffsetInBytes,Stride);
	}

	HRESULT __stdcall GetStreamSource(UINT StreamNumber,IDirect3DVertexBuffer9** ppStreamData,UINT* OffsetInBytes,UINT* pStride)
	{
		return m_real->GetStreamSource(StreamNumber,ppStreamData,OffsetInBytes,pStride);
	}

	HRESULT __stdcall SetStreamSourceFreq(UINT StreamNumber,UINT Divider)
	{
		return m_real->SetStreamSourceFreq(StreamNumber,Divider);
	}

	HRESULT __stdcall GetStreamSourceFreq(UINT StreamNumber,UINT* Divider)
	{
		return m_real->GetStreamSourceFreq(StreamNumber,Divider);
	}

	HRESULT __stdcall SetIndices(IDirect3DIndexBuffer9* pIndexData)
	{
		return m_real->SetIndices(pIndexData);
	}

	HRESULT __stdcall GetIndices(IDirect3DIndexBuffer9** ppIndexData)
	{
		return m_real->GetIndices(ppIndexData);
	}

	HRESULT __stdcall CreatePixelShader(CONST DWORD* pFunction,IDirect3DPixelShader9** ppShader)
	{
		return m_real->CreatePixelShader(pFunction,ppShader);
	}

	HRESULT __stdcall SetPixelShader(IDirect3DPixelShader9* pShader)
	{
		return m_real->SetPixelShader(pShader);
	}

	HRESULT __stdcall GetPixelShader(IDirect3DPixelShader9** ppShader)
	{
		return m_real->GetPixelShader(ppShader);
	}

	HRESULT __stdcall SetPixelShaderConstantF(UINT StartRegister,CONST float* pConstantData,UINT Vector4fCount)
	{
		return m_real->SetPixelShaderConstantF(StartRegister,pConstantData,Vector4fCount);
	}

	HRESULT __stdcall GetPixelShaderConstantF(UINT StartRegister,float* pConstantData,UINT Vector4fCount)
	{
		return m_real->GetPixelShaderConstantF(StartRegister,pConstantData,Vector4fCount);
	}

	HRESULT __stdcall SetPixelShaderConstantI(UINT StartRegister,CONST int* pConstantData,UINT Vector4iCount)
	{
		return m_real->SetPixelShaderConstantI(StartRegister,pConstantData,Vector4iCount);
	}

	HRESULT __stdcall GetPixelShaderConstantI(UINT StartRegister,int* pConstantData,UINT Vector4iCount)
	{
		return m_real->GetPixelShaderConstantI(StartRegister,pConstantData,Vector4iCount);
	}

	HRESULT __stdcall SetPixelShaderConstantB(UINT StartRegister,CONST BOOL* pConstantData,UINT  BoolCount)
	{
		return m_real->SetPixelShaderConstantB(StartRegister,pConstantData,BoolCount);
	}

	HRESULT __stdcall GetPixelShaderConstantB(UINT StartRegister,BOOL* pConstantData,UINT BoolCount)
	{
		return m_real->GetPixelShaderConstantB(StartRegister,pConstantData,BoolCount);
	}

	HRESULT __stdcall DrawRectPatch(UINT Handle,CONST float* pNumSegs,CONST D3DRECTPATCH_INFO* pRectPatchInfo)
	{
		return m_real->DrawRectPatch(Handle,pNumSegs, pRectPatchInfo);
	}

	HRESULT __stdcall DrawTriPatch(UINT Handle,CONST float* pNumSegs,CONST D3DTRIPATCH_INFO* pTriPatchInfo)
	{
		return m_real->DrawTriPatch(Handle, pNumSegs, pTriPatchInfo);
	}

	HRESULT __stdcall DeletePatch(UINT Handle)
	{
		return m_real->DeletePatch(Handle);
	}

	HRESULT __stdcall CreateQuery(D3DQUERYTYPE Type,IDirect3DQuery9** ppQuery)
	{
		return m_real->CreateQuery(Type,ppQuery);
	}
};
#endif // _D3DCUTTER_D3D9CUTTER_H_